package com.swanclouds.redfish.managers;

import com.google.common.base.Preconditions;
import com.swanclouds.api.Apis;
import com.swanclouds.api.managers.*;
import com.swanclouds.core.transport.ClientConstants;
import com.swanclouds.core.transport.HttpResponse;
import com.swanclouds.model.common.ActionResponse;
import com.swanclouds.model.managers.Configuration;
import com.swanclouds.model.managers.Managers;
import com.swanclouds.model.managers.RestoreFactory;
import com.swanclouds.redfish.common.redfish.PowerOnPermit;
import com.swanclouds.redfish.common.redfish.ResetType;
import com.swanclouds.redfish.internal.BaseManagerService;
import com.swanclouds.redfish.managers.domain.ManagerModel;

import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;

public class ManagerServiceImpl extends BaseManagerService implements ManagerService {

    /**
     *查询特定的管理资源信息
     * @return Managers
     */
    @Override
    public Managers get() {
        return get(ManagerModel.class,uri(ClientConstants.PATH_MANAGERS_ID,getManagerId())).execute();
    }

    /**
     * 操作网络协议服务
     * @return NetworkProtocolService
     */
    @Override
    public NetworkProtocolService NetworkProtocol() {
        return Apis.get(NetworkProtocolService.class);
    }

    /**
     * 操作以太网接口服务
     * @return EthernetInterfacesService
     */
    @Override
    public EthernetInterfacesService EthernetInterfaces() {
        return Apis.get(EthernetInterfacesService.class);
    }

    /**
     * 操作虚拟媒体服务
     * @return VirtualMediaService
     */
    @Override
    public VirtualMediaService VirtualMedia() {
        return Apis.get(VirtualMediaService.class);
    }

    /**
     * 操作日志服务
     * @return LogService
     */
    @Override
    public LogService LogInformation() {
        return Apis.get(LogService.class);
    }

    /**
     * 操作安全服务
     * @return SecurityService
     */
    @Override
    public SecurityService SecurityService() {
        return Apis.get(SecurityService.class);
    }

    /**
     * 操作Snm服务
     * @return SnmpService
     */
    @Override
    public SnmpService SnmpService() {
        return Apis.get(SnmpService.class);
    }

    /**
     * 操作Smt服务
     * @return SmtpService
     */
    @Override
    public SmtpService SmtpService() {
        return Apis.get(SmtpService.class);
    }

    /**
     * 操作KVM服务
     * @return KvmService
     */
    @Override
    public KvmService KvmService() {
        return Apis.get(KvmService.class);
    }

    /**
     * 操作Ntp服务
     * @return NtpService
     */
    @Override
    public NtpService NtpService() {
        return Apis.get(NtpService.class);
    }

    /**
     * 重启iBMC 只可选择强制重启
     * @param resetType 重启的参数 resetType = ForceRestart
     * @return ActionResponse
     */
    @Override
    public ActionResponse managerReset(ResetType resetType) {
        Preconditions.checkNotNull(resetType, "resetType is null");
        return post(ActionResponse.class,uri(ClientConstants.PATH_MANAGERS_RESET,getManagerId())).entity(resetType).execute();
    }

    /**
     * 服务器切换iBMC镜像
     * @return ActionResponse
     */
    @Override
    public ActionResponse managerRollBack() {
       return post(ActionResponse.class,uri(ClientConstants.PATH_MANAGERS_ROLLBACK,getManagerId()))/*.entity()*/.execute();
    }

    /**
     * 服务器受控上电
     * @param powerOnPermit  On("On","上电") Off("Off","下电");
     * @return ActionResponse
     */
    @Override
    public ActionResponse managerPowerOnPermit(PowerOnPermit powerOnPermit) {
        Preconditions.checkNotNull(powerOnPermit, "resetType is null");
        return post(ActionResponse.class,uri(ClientConstants.PATH_MANAGERS_POWERONPERMIT)).entity(powerOnPermit).execute();
    }

    /**
     * Syslog服务信息
     * @return SyslogService
     */
    @Override
    public SyslogService SyslogService() {
        return Apis.get(SyslogService.class);
    }

    @Override
    public LldpService LldpService() {
        return Apis.get(LldpService.class);
    }

    /**
     * 修改管理资源信息
     * @param model 修改管理资源参数 dateTime dateTimeLocalOffset graphicalConsole
     * @return Managers  未实现
     */
    @Override
    public Managers updateManagers(ManagerModel model) {
        //确保获取到的if-Match是最新的
        Preconditions.checkNotNull(model,"model is null");
        Preconditions.checkNotNull(model.getDateTime(),"dateTime is null");
        Preconditions.checkNotNull(model.getDateTimeLocalOffset(),"dateTimeLocalOffset is null");
        get();
        return patch(ManagerModel.class,uri(ClientConstants.PATH_MANAGERS_ID,getManagerId())).entity(model).execute();
    }

    /**
     * 查询诊断服务
     * @return DiagnosticService
     */
    @Override
    public DiagnosticService DiagnosticService() {
        return Apis.get(DiagnosticService.class);
    }

    /**
     * 恢复出厂设置
     * @param restoreFactory 恢复出厂设置参数
     * @return ActionResponse
     */
    @Override
    public ActionResponse restoreFactory(RestoreFactory restoreFactory) {
        return post(ActionResponse.class,uri(ClientConstants.PATH_MANAGERS_RESTOREFATORY,getManagerId())).entity(restoreFactory).execute();
    }

    /**
     * 导入配置文件
     * @param configuration 导入文件路径 类型
     * @return ActionResponse
     */
    @Override
    public ActionResponse importConfiguration(Configuration configuration) {
        Preconditions.checkNotNull(configuration.getContent(),"content is null");
        Preconditions.checkNotNull(configuration.getType(),"type is null");
        return post(ActionResponse.class,uri(ClientConstants.PATH_MANAGERS_IMPORTCONFIGURATION,getManagerId())).entity(configuration).execute();
    }

    /**
     * 导出配置文件
     * @param configuration 导出文件路径 类型
     * @return ActionResponse
     */
    @Override
    public ActionResponse exportConfiguration(Configuration configuration) {
        Preconditions.checkNotNull(configuration.getContent(), "content is null");
        Preconditions.checkNotNull(configuration.getType(),"type is null");
        HttpResponse response = post(Void.class, uri(ClientConstants.PATH_MANAGERS_EXPORTCONFIGURATION, getManagerId()))
                .header(ClientConstants.HEADER_CONTENT_TYPE, ClientConstants.CONTENT_TYPE_JSON_CHARSET)
                .entity(configuration)
                .executeWithResponse();
        if (response.getStatus() < 400) {
            InputStream inputStream = response.getInputStream();
            OutputStream outputStream;
            try {
                outputStream = new FileOutputStream("");
                byte[] buffer = new byte[1024];
                int bytesRead;
                while ((bytesRead = inputStream.read(buffer)) != -1) {
                    outputStream.write(buffer, 0, bytesRead);
                }
                inputStream.close();
                outputStream.flush();
                outputStream.close();
                return ActionResponse.actionSuccess();
            } catch (Exception e) {
                e.printStackTrace();
                return ActionResponse.actionFailed("Failed to write to file " + e.getMessage(), 400);
            }
        } else {
            return ActionResponse.actionFailed(response.getStatusMessage(),response.getStatus());
        }
    }
}
